/*
Copyright (C) 2006 - 2014 Evan Teran
                          eteran@alum.rit.edu

This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program.  If not, see <http://www.gnu.org/licenses/>.
*/

#ifndef OPTABLE_FPU_20080314_TCC_
#define OPTABLE_FPU_20080314_TCC_

namespace edisassm {

// this table is for x87 opcodes with a mod < 0xc0
template <class M>
const typename Instruction<M>::opcode_entry Instruction<M>::Opcodes_x87_Lo[64] = {

	/* 0xd8 0x00 - 0xd8 0xbf */
	{ "fadd",  &Instruction::decode_SingleReal, OP_FADD,  FLAG_FPU },
	{ "fmul",  &Instruction::decode_SingleReal, OP_FMUL,  FLAG_FPU },
	{ "fcom",  &Instruction::decode_SingleReal, OP_FCOM,  FLAG_FPU },
	{ "fcomp", &Instruction::decode_SingleReal, OP_FCOMP, FLAG_FPU },
	{ "fsub",  &Instruction::decode_SingleReal, OP_FSUB,  FLAG_FPU },
	{ "fsubr", &Instruction::decode_SingleReal, OP_FSUBR, FLAG_FPU },
	{ "fdiv",  &Instruction::decode_SingleReal, OP_FDIV,  FLAG_FPU },
	{ "fdivr", &Instruction::decode_SingleReal, OP_FDIVR, FLAG_FPU },

	/* 0xd9 0x00 - 0xd9 0xbf */
	{ "fld",     &Instruction::decode_SingleReal, OP_FLD,     FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,    OP_INVALID, FLAG_NONE },
	{ "fst",     &Instruction::decode_SingleReal, OP_FST,     FLAG_FPU },
	{ "fstp",    &Instruction::decode_SingleReal, OP_FSTP,    FLAG_FPU },
	{ "fldenv",  &Instruction::decode_M28,        OP_FLDENV,  FLAG_FPU },
	{ "fldcw",   &Instruction::decode_Mw,         OP_FLDCW,   FLAG_FPU },
	{ "fnstenv", &Instruction::decode_M28,        OP_FNSTENV, FLAG_FPU },
	{ "fnstcw",  &Instruction::decode_Mw,         OP_FNSTCW,  FLAG_FPU },

	/* 0xda 0x00 - 0xda 0xbf */
	{ "fiadd",  &Instruction::decode_ShortInteger, OP_FIADD,  FLAG_FPU },
	{ "fimul",  &Instruction::decode_ShortInteger, OP_FIMUL,  FLAG_FPU },
	{ "ficom",  &Instruction::decode_ShortInteger, OP_FICOM,  FLAG_FPU },
	{ "ficomp", &Instruction::decode_ShortInteger, OP_FICOMP, FLAG_FPU },
	{ "fisub",  &Instruction::decode_ShortInteger, OP_FISUB,  FLAG_FPU },
	{ "fisubr", &Instruction::decode_ShortInteger, OP_FISUBR, FLAG_FPU },
	{ "fidiv",  &Instruction::decode_ShortInteger, OP_FIDIV,  FLAG_FPU },
	{ "fidivr", &Instruction::decode_ShortInteger, OP_FIDIVR, FLAG_FPU },

	/* 0xdb 0x00 - 0xdb 0xbf */
	{ "fild",    &Instruction::decode_ShortInteger, OP_FILD,    FLAG_FPU },
	{ "fisttp",  &Instruction::decode_ShortInteger, OP_FISTTP,  FLAG_FPU | FLAG_SSE3 },
	{ "fist",    &Instruction::decode_ShortInteger, OP_FIST,    FLAG_FPU },
	{ "fistp",   &Instruction::decode_ShortInteger, OP_FISTP,   FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,      OP_INVALID, FLAG_NONE },
	{ "fld",     &Instruction::decode_ExtendedReal, OP_FLD,     FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,      OP_INVALID, FLAG_NONE },
	{ "fstp",    &Instruction::decode_ExtendedReal, OP_FSTP,    FLAG_FPU },

	/* 0xdc 0x00 - 0xdc 0xbf */
	{ "fadd",  &Instruction::decode_DoubleReal, OP_FADD,  FLAG_FPU },
	{ "fmul",  &Instruction::decode_DoubleReal, OP_FMUL,  FLAG_FPU },
	{ "fcom",  &Instruction::decode_DoubleReal, OP_FCOM,  FLAG_FPU },
	{ "fcomp", &Instruction::decode_DoubleReal, OP_FCOMP, FLAG_FPU },
	{ "fsub",  &Instruction::decode_DoubleReal, OP_FSUB,  FLAG_FPU },
	{ "fsubr", &Instruction::decode_DoubleReal, OP_FSUBR, FLAG_FPU },
	{ "fdiv",  &Instruction::decode_DoubleReal, OP_FDIV,  FLAG_FPU },
	{ "fdivr", &Instruction::decode_DoubleReal, OP_FDIVR, FLAG_FPU },

	/* 0xdd 0x00 - 0xdd 0xbf */
	{ "fld",     &Instruction::decode_DoubleReal,  OP_FLD,     FLAG_FPU },
	{ "fisttp",  &Instruction::decode_LongInteger, OP_FISTTP,  FLAG_FPU | FLAG_SSE3 },
	{ "fst",     &Instruction::decode_DoubleReal,  OP_FST,     FLAG_FPU },
	{ "fstp",    &Instruction::decode_DoubleReal,  OP_FSTP,    FLAG_FPU },
	{ "frstor",  &Instruction::decode_M108,        OP_FRSTOR,  FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,     OP_INVALID, FLAG_NONE },
	{ "fnsave",  &Instruction::decode_M108,        OP_FNSAVE,  FLAG_FPU },
	{ "fnstsw",  &Instruction::decode_Mw,          OP_FNSTSW,  FLAG_FPU },

	/* 0xde 0x00 - 0xde 0xbf */
	{ "fiadd",  &Instruction::decode_WordInteger, OP_FIADD,  FLAG_FPU },
	{ "fimul",  &Instruction::decode_WordInteger, OP_FIMUL,  FLAG_FPU },
	{ "ficom",  &Instruction::decode_WordInteger, OP_FICOM,  FLAG_FPU },
	{ "ficomp", &Instruction::decode_WordInteger, OP_FICOMP, FLAG_FPU },
	{ "fisub",  &Instruction::decode_WordInteger, OP_FISUB,  FLAG_FPU },
	{ "fisubr", &Instruction::decode_WordInteger, OP_FISUBR, FLAG_FPU },
	{ "fidiv",  &Instruction::decode_WordInteger, OP_FIDIV,  FLAG_FPU },
	{ "fidivr", &Instruction::decode_WordInteger, OP_FIDIVR, FLAG_FPU },

	/* 0xdf 0x00 - 0xdf 0xbf */
	{ "fild",   &Instruction::decode_WordInteger, OP_FILD,   FLAG_FPU },
	{ "fisttp", &Instruction::decode_WordInteger, OP_FISTTP, FLAG_FPU | FLAG_SSE3 },
	{ "fist",   &Instruction::decode_WordInteger, OP_FIST,   FLAG_FPU },
	{ "fistp",  &Instruction::decode_WordInteger, OP_FISTP,  FLAG_FPU },
	{ "fbld",   &Instruction::decode_PackedBCD,   OP_FBLD,   FLAG_FPU },
	{ "fild",   &Instruction::decode_LongInteger, OP_FILD,   FLAG_FPU },
	{ "fbstp",  &Instruction::decode_PackedBCD,   OP_FBSTP,  FLAG_FPU },
	{ "fistp",  &Instruction::decode_LongInteger, OP_FISTP,  FLAG_FPU },
};

// this table is for x87 opcodes with a mod >= 0xc0
template <class M>
const typename Instruction<M>::opcode_entry Instruction<M>::Opcodes_x87_Hi[0x200] = {

	/* 0xd8 0xc0 - 0xd8 0xff */
	{ "fadd",  &Instruction::template decode_ST_STi<0>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<1>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<2>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<3>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<4>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<5>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<6>, OP_FADD,  FLAG_FPU },
	{ "fadd",  &Instruction::template decode_ST_STi<7>, OP_FADD,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<0>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<1>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<2>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<3>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<4>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<5>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<6>, OP_FMUL,  FLAG_FPU },
	{ "fmul",  &Instruction::template decode_ST_STi<7>, OP_FMUL,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<0>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<1>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<2>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<3>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<4>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<5>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<6>,    OP_FCOM,  FLAG_FPU },
	{ "fcom",  &Instruction::template decode_STi<7>,    OP_FCOM,  FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<0>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<1>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<2>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<3>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<4>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<5>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<6>,    OP_FCOMP, FLAG_FPU },
	{ "fcomp", &Instruction::template decode_STi<7>,    OP_FCOMP, FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<0>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<1>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<2>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<3>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<4>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<5>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<6>, OP_FSUB,  FLAG_FPU },
	{ "fsub",  &Instruction::template decode_ST_STi<7>, OP_FSUB,  FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<0>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<1>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<2>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<3>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<4>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<5>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<6>, OP_FSUBR, FLAG_FPU },
	{ "fsubr", &Instruction::template decode_ST_STi<7>, OP_FSUBR, FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<0>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<1>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<2>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<3>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<4>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<5>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<6>, OP_FDIV,  FLAG_FPU },
	{ "fdiv",  &Instruction::template decode_ST_STi<7>, OP_FDIV,  FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<0>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<1>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<2>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<3>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<4>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<5>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<6>, OP_FDIVR, FLAG_FPU },
	{ "fdivr", &Instruction::template decode_ST_STi<7>, OP_FDIVR, FLAG_FPU },

	/* 0xd9 0xc0 - 0xd9 0xff */
	{ "fld",     &Instruction::template decode_STi<0>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<1>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<2>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<3>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<4>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<5>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<6>, OP_FLD,     FLAG_FPU },
	{ "fld",     &Instruction::template decode_STi<7>, OP_FLD,     FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<0>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<1>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<2>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<3>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<4>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<5>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<6>, OP_FXCH,    FLAG_FPU },
	{ "fxch",    &Instruction::template decode_STi<7>, OP_FXCH,    FLAG_FPU },
	{ "fnop",    &Instruction::decode0,                OP_FNOP,    FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "fstpnce", &Instruction::template decode_STi_ST<0>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<1>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<2>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<3>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<4>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<5>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<6>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fstpnce", &Instruction::template decode_STi_ST<7>, OP_FSTPNCE,    FLAG_FPU }, // TODO: is param order correct?
	{ "fchs",    &Instruction::decode0,                OP_FCHS,    FLAG_FPU },
	{ "fabs",    &Instruction::decode0,                OP_FABS,    FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "ftst",    &Instruction::decode0,                OP_FTST,    FLAG_FPU },
	{ "fxam",    &Instruction::decode0,                OP_FXAM,    FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "fld1",    &Instruction::decode0,                OP_FLD1,    FLAG_FPU },
	{ "fldl2t",  &Instruction::decode0,                OP_FLDL2T,  FLAG_FPU },
	{ "fldl2e",  &Instruction::decode0,                OP_FLDL2E,  FLAG_FPU },
	{ "fldpi",   &Instruction::decode0,                OP_FLDPI,   FLAG_FPU },
	{ "fldlg2",  &Instruction::decode0,                OP_FLDLG2,  FLAG_FPU },
	{ "fldln2",  &Instruction::decode0,                OP_FLDLN2,  FLAG_FPU },
	{ "fldz",    &Instruction::decode0,                OP_FLDZ,    FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "f2xm1",   &Instruction::decode0,                OP_F2XM1,   FLAG_FPU },
	{ "fyl2x",   &Instruction::decode0,                OP_FYL2X,   FLAG_FPU },
	{ "fptan",   &Instruction::decode0,                OP_FPTAN,   FLAG_FPU },
	{ "fpatan",  &Instruction::decode0,                OP_FPATAN,  FLAG_FPU },
	{ "fxtract", &Instruction::decode0,                OP_FXTRACT, FLAG_FPU },
	{ "fprem1",  &Instruction::decode0,                OP_FPREM1,  FLAG_FPU },
	{ "fdecstp", &Instruction::decode0,                OP_FDECSTP, FLAG_FPU },
	{ "fincstp", &Instruction::decode0,                OP_FINCSTP, FLAG_FPU },
	{ "fprem",   &Instruction::decode0,                OP_FPREM,   FLAG_FPU },
	{ "fyl2xp1", &Instruction::decode0,                OP_FYL2XP1, FLAG_FPU },
	{ "fsqrt",   &Instruction::decode0,                OP_FSQRT,   FLAG_FPU },
	{ "fsincos", &Instruction::decode0,                OP_FSINCOS, FLAG_FPU },
	{ "frndint", &Instruction::decode0,                OP_FRNDINT, FLAG_FPU },
	{ "fscale",  &Instruction::decode0,                OP_FSCALE,  FLAG_FPU },
	{ "fsin",    &Instruction::decode0,                OP_FSIN,    FLAG_FPU },
	{ "fcos",    &Instruction::decode0,                OP_FCOS,    FLAG_FPU },

	/* 0xda 0xc0 - 0xda 0xff */
	{ "fcmovb",  &Instruction::template decode_ST_STi<0>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<1>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<2>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<3>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<4>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<5>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<6>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmovb",  &Instruction::template decode_ST_STi<7>, OP_FCMOVB,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<0>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<1>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<2>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<3>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<4>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<5>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<6>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmove",  &Instruction::template decode_ST_STi<7>, OP_FCMOVE,  FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<0>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<1>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<2>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<3>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<4>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<5>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<6>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovbe", &Instruction::template decode_ST_STi<7>, OP_FCMOVBE, FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<0>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<1>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<2>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<3>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<4>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<5>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<6>, OP_FCMOVU,  FLAG_FPU },
	{ "fcmovu",  &Instruction::template decode_ST_STi<7>, OP_FCMOVU,  FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fucompp", &Instruction::decode0,                   OP_FUCOMPP, FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },


	/* 0xdb 0xc0 - 0xdb 0xff */
	{ "fcmovnb", &Instruction::template decode_ST_STi<0>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<1>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<2>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<3>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<4>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<5>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<6>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovnb", &Instruction::template decode_ST_STi<7>, OP_FCMOVNB,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<0>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<1>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<2>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<3>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<4>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<5>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<6>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovne", &Instruction::template decode_ST_STi<7>, OP_FCMOVNE,  FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<0>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<1>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<2>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<3>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<4>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<5>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<6>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnbe",&Instruction::template decode_ST_STi<7>, OP_FCMOVNBE, FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<0>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<1>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<2>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<3>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<4>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<5>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<6>, OP_FCMOVNU,  FLAG_FPU },
	{ "fcmovnu", &Instruction::template decode_ST_STi<7>, OP_FCMOVNU,  FLAG_FPU },
	{ "fneni",   &Instruction::decode0,                   OP_FNENI,    FLAG_FPU },
	{ "fndisi",  &Instruction::decode0,                   OP_FNDISI,   FLAG_FPU },
	{ "fnclex",  &Instruction::decode0,                   OP_FNCLEX,   FLAG_FPU },
	{ "fninit",  &Instruction::decode0,                   OP_FNINIT,   FLAG_FPU },
	{ "fnsetpm", &Instruction::decode0,                   OP_FNSETPM,  FLAG_286_ONLY | FLAG_FPU }, // 286 only
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "fucomi",  &Instruction::template decode_ST_STi<0>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<1>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<2>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<3>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<4>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<5>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<6>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomi",  &Instruction::template decode_ST_STi<7>, OP_FUCOMI,   FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<0>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<1>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<2>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<3>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<4>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<5>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<6>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomi",   &Instruction::template decode_ST_STi<7>, OP_FCOMI,    FLAG_FPU | FLAG_W_FLAGS },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID,  FLAG_NONE },

	/* 0xdc 0xc0 - 0xdc 0xff */
	{ "fadd",    &Instruction::template decode_STi_ST<0>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<1>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<2>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<3>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<4>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<5>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<6>, OP_FADD,    FLAG_FPU },
	{ "fadd",    &Instruction::template decode_STi_ST<7>, OP_FADD,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<0>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<1>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<2>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<3>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<4>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<5>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<6>, OP_FMUL,    FLAG_FPU },
	{ "fmul",    &Instruction::template decode_STi_ST<7>, OP_FMUL,    FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fsubr",   &Instruction::template decode_STi_ST<0>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<1>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<2>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<3>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<4>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<5>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<6>, OP_FSUBR,   FLAG_FPU },
	{ "fsubr",   &Instruction::template decode_STi_ST<7>, OP_FSUBR,   FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<0>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<1>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<2>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<3>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<4>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<5>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<6>, OP_FSUB,    FLAG_FPU },
	{ "fsub",    &Instruction::template decode_STi_ST<7>, OP_FSUB,    FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<0>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<1>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<2>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<3>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<4>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<5>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<6>, OP_FDIVR,   FLAG_FPU },
	{ "fdivr",   &Instruction::template decode_STi_ST<7>, OP_FDIVR,   FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<0>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<1>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<2>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<3>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<4>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<5>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<6>, OP_FDIV,    FLAG_FPU },
	{ "fdiv",    &Instruction::template decode_STi_ST<7>, OP_FDIV,    FLAG_FPU },

	/* 0xdd 0xc0 - 0xdd 0xff */
	{ "ffree",   &Instruction::template decode_STi<0>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<1>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<2>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<3>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<4>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<5>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<6>, OP_FFREE,   FLAG_FPU },
	{ "ffree",   &Instruction::template decode_STi<7>, OP_FFREE,   FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "fst",     &Instruction::template decode_STi<0>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<1>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<2>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<3>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<4>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<5>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<6>, OP_FST,     FLAG_FPU },
	{ "fst",     &Instruction::template decode_STi<7>, OP_FST,     FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<0>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<1>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<2>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<3>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<4>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<5>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<6>, OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi<7>, OP_FSTP,    FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<0>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<1>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<2>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<3>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<4>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<5>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<6>, OP_FUCOM,   FLAG_FPU },
	{ "fucom",   &Instruction::template decode_STi<7>, OP_FUCOM,   FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<0>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<1>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<2>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<3>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<4>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<5>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<6>, OP_FUCOMP,  FLAG_FPU },
	{ "fucomp",  &Instruction::template decode_STi<7>, OP_FUCOMP,  FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,         OP_INVALID, FLAG_NONE },

	/* 0xde 0xc0 - 0xde 0xff */
	{ "faddp",   &Instruction::template decode_STi_ST<0>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<1>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<2>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<3>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<4>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<5>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<6>, OP_FADDP,   FLAG_FPU },
	{ "faddp",   &Instruction::template decode_STi_ST<7>, OP_FADDP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<0>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<1>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<2>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<3>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<4>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<5>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<6>, OP_FMULP,   FLAG_FPU },
	{ "fmulp",   &Instruction::template decode_STi_ST<7>, OP_FMULP,   FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fcompp",  &Instruction::decode0,                   OP_FCOMPP,  FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fsubrp",  &Instruction::template decode_STi_ST<0>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<1>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<2>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<3>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<4>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<5>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<6>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubrp",  &Instruction::template decode_STi_ST<7>, OP_FSUBRP,  FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<0>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<1>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<2>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<3>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<4>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<5>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<6>, OP_FSUBP,   FLAG_FPU },
	{ "fsubp",   &Instruction::template decode_STi_ST<7>, OP_FSUBP,   FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<0>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<1>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<2>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<3>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<4>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<5>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<6>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivrp",  &Instruction::template decode_STi_ST<7>, OP_FDIVRP,  FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<0>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<1>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<2>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<3>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<4>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<5>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<6>, OP_FDIVP,   FLAG_FPU },
	{ "fdivp",   &Instruction::template decode_STi_ST<7>, OP_FDIVP,   FLAG_FPU },

	/* 0xdf 0xc0 - 0xdf 0xff */
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fstp",    &Instruction::template decode_STi_ST<0>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<1>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<2>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<3>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<4>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<5>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<6>,  OP_FSTP,    FLAG_FPU },
	{ "fstp",    &Instruction::template decode_STi_ST<7>,  OP_FSTP,    FLAG_FPU },
	{ "fnstsw",  &Instruction::decode_AX,                 OP_FNSTSW,  FLAG_FPU },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "fucomip", &Instruction::template decode_ST_STi<0>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<1>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<2>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<3>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<4>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<5>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<6>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fucomip", &Instruction::template decode_ST_STi<7>, OP_FUCOMIP, FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<0>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<1>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<2>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<3>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<4>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<5>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<6>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "fcomip",  &Instruction::template decode_ST_STi<7>, OP_FCOMIP,  FLAG_FPU | FLAG_W_FLAGS },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
	{ "invalid", &Instruction::decode_invalid,            OP_INVALID, FLAG_NONE },
};

}

#endif
